# -*- coding: utf-8 -*-

import json
import logging
from datetime import datetime
from odoo import http, fields
from odoo.http import request
from odoo.exceptions import ValidationError, AccessError
from .api_base import api_response, verify_api_token, check_department_permission
import io

_logger = logging.getLogger(__name__)


class RepairController(http.Controller):
    """设备报修管理控制器"""

    @http.route('/api/repair/list', type='json', auth='none', methods=['POST'], csrf=False, cors='*')
    # @api_response
    @verify_api_token
    # @check_api_permission('device:repair:list')  # 已注释按钮权限，改用部门权限
    @check_department_permission
    def list_repair(self, **kwargs):
        """获取设备报修列表"""
        page = kwargs.get('pageNum', 1)
        size = kwargs.get('pageSize', 10)
        equipment_id = kwargs.get('equipmentId', '')
        equipment_name = kwargs.get('equipmentName', '')
        reporter_name = kwargs.get('reporterName', '')
        status = kwargs.get('status', '')
        fault_type = kwargs.get('faultType', '')
        urgency = kwargs.get('urgency', '')
        start_date = kwargs.get('startDate', '')
        end_date = kwargs.get('endDate', '')

        domain = []
        if equipment_id:
            domain.append(('equipment_id', '=', int(equipment_id)))
        if equipment_name:
            domain.append(('equipment_name', 'ilike', equipment_name))
        if reporter_name:
            domain.append(('reporter_name', 'ilike', reporter_name))
        if status:
            domain.append(('status', '=', status))
        if fault_type:
            domain.append(('fault_type', '=', fault_type))
        if urgency:
            domain.append(('urgency', '=', urgency))
        if start_date:
            domain.append(('repair_date', '>=', start_date))
        if end_date:
            domain.append(('repair_date', '<=', end_date))

        # 部门权限过滤
        current_user = getattr(request, 'current_api_user', None)
        if current_user:
            # 检查是否是admin账号，admin账号拥有全部权限
            if hasattr(current_user, 'is_admin') and current_user.is_admin:
                # admin账号可以看到所有报修记录，不添加过滤条件
                pass
            else:
                user_department = current_user.department_id
                if user_department:
                    # 检查用户是否是部门负责人
                    is_department_leader = user_department.leader_id and user_department.leader_id.id == current_user.id

                    if is_department_leader:
                        # 部门负责人：可以看到该部门下的所有设备相关报修
                        equipment_ids = request.env['device.equipment'].search([
                            ('department_id', '=', user_department.id)
                        ]).ids
                        if equipment_ids:
                            domain.append(('equipment_id', 'in', equipment_ids))
                        else:
                            domain.append(('id', '=', False))
                    else:
                        # 非部门负责人：只能看到设备绑定用户为自己的报修记录
                        equipment_ids = request.env['device.equipment'].search([
                            ('user_id', '=', current_user.id)
                        ]).ids
                        if equipment_ids:
                            domain.append(('equipment_id', 'in', equipment_ids))
                        else:
                            # 如果没有绑定设备，返回空结果
                            domain.append(('id', '=', False))
                else:
                    # 没有部门信息，返回空结果
                    domain.append(('id', '=', False))

        # 计算总数
        total = request.env['device.repair'].sudo().search_count(domain)

        # 获取数据
        offset = (page - 1) * size
        repairs = request.env['device.repair'].sudo().search(domain, offset=offset, limit=size,
                                                             order='repair_date desc')

        # 构建返回数据
        rows = []
        for repair in repairs:
            rows.append({
                'repairId': repair.id,
                'equipmentId': repair.equipment_id.id,
                'equipmentName': repair.equipment_name,
                'equipmentCode': repair.equipment_code,
                'equipmentCategory': repair.equipment_category,
                'equipmentModel': repair.equipment_model,
                'repairDate': repair.repair_date.strftime('%Y-%m-%d %H:%M:%S') if repair.repair_date else '',
                'repairContent': repair.repair_content or '',
                'reporterId': repair.reporter_id.id if repair.reporter_id else None,
                'reporterName': repair.reporter_name,
                'contactPhone': repair.contact_phone or '',
                'faultType': repair.fault_type,
                'urgency': repair.urgency,
                'status': repair.status,
                'assignedTo': repair.assigned_to.nick_name if repair.assigned_to else '',
                'assignedDate': repair.assigned_date.strftime('%Y-%m-%d %H:%M:%S') if repair.assigned_date else '',
                'repairStartDate': repair.repair_start_date.strftime(
                    '%Y-%m-%d %H:%M:%S') if repair.repair_start_date else '',
                'repairEndDate': repair.repair_end_date.strftime('%Y-%m-%d %H:%M:%S') if repair.repair_end_date else '',
                'downtimeHours': repair.downtime_hours,
                'estimatedCost': repair.estimated_cost,
                'actualCost': repair.actual_cost,
                'createTime': repair.create_time.strftime('%Y-%m-%d %H:%M:%S') if repair.create_time else '',
                'remark': repair.remark or ''
            })
        return {
            'code': 200,
            'msg': '查询成功',
            'data': {
                'total': total,
                'rows': rows
            }
        }

    @http.route('/api/repair/info/<int:repair_id>', type='json', auth='none', methods=['POST'], csrf=False, cors='*')
    # @api_response
    @verify_api_token
    # @check_api_permission('device:repair:read')  # 已注释按钮权限，改用部门权限
    @check_department_permission
    def get_repair(self, repair_id, **kwargs):
        """获取报修详情"""
        repair = request.env['device.repair'].sudo().browse(repair_id)
        if not repair.exists():
            raise ValidationError('报修记录不存在')

        data = {
            'repairId': repair.id,
            'equipmentId': repair.equipment_id.id,
            'equipmentName': repair.equipment_name,
            'equipmentCode': repair.equipment_code,
            'equipmentCategory': repair.equipment_category,
            'equipmentModel': repair.equipment_model,
            'repairDate': repair.repair_date.strftime('%Y-%m-%d %H:%M:%S') if repair.repair_date else '',
            'repairContent': repair.repair_content or '',
            'reporterId': repair.reporter_id.id if repair.reporter_id else None,
            'reporterName': repair.reporter_name,
            'contactPhone': repair.contact_phone or '',
            'faultType': repair.fault_type,
            'urgency': repair.urgency,
            'status': repair.status,
            'assignedTo': repair.assigned_to.id if repair.assigned_to else None,
            'assignedToName': repair.assigned_to.nick_name if repair.assigned_to else '',
            'assignedDate': repair.assigned_date.strftime('%Y-%m-%d %H:%M:%S') if repair.assigned_date else '',
            'repairStartDate': repair.repair_start_date.strftime(
                '%Y-%m-%d %H:%M:%S') if repair.repair_start_date else '',
            'repairEndDate': repair.repair_end_date.strftime('%Y-%m-%d %H:%M:%S') if repair.repair_end_date else '',
            'faultAnalysis': repair.fault_analysis or '',
            'repairSolution': repair.repair_solution or '',
            'repairProcess': repair.repair_process or '',
            'repairResult': repair.repair_result or '',
            'estimatedCost': repair.estimated_cost,
            'actualCost': repair.actual_cost,
            'partsCost': repair.parts_cost,
            'laborCost': repair.labor_cost,
            'downtimeHours': repair.downtime_hours,
            'createTime': repair.create_time.strftime('%Y-%m-%d %H:%M:%S') if repair.create_time else '',
            'updateTime': repair.update_time.strftime('%Y-%m-%d %H:%M:%S') if repair.update_time else '',
            'createBy': repair.create_by,
            'updateBy': repair.update_by,
            'remark': repair.remark or ''
        }
        return {
            'code': 200,
            'msg': '查询成功',
            'data': data
        }

    @http.route('/api/repair/add', type='json', auth='none', methods=['POST'], csrf=False, cors='*')
    # @api_response
    @verify_api_token
    # @check_api_permission('device:repair:add')  # 已注释按钮权限，改用部门权限
    @check_department_permission
    def add_repair(self, **kwargs):
        """新增报修记录"""
        equipment_id = kwargs.get('equipmentId')
        repair_content = kwargs.get('repairContent')
        reporter_id = kwargs.get('reporterId')
        contact_phone = kwargs.get('contactPhone', '')
        fault_type = kwargs.get('faultType')
        urgency = kwargs.get('urgency', 'medium')
        estimated_cost = kwargs.get('estimatedCost', 0.0)
        remark = kwargs.get('remark', '')

        if not equipment_id or not repair_content or not reporter_id or not fault_type:
            raise ValidationError('设备、报修内容、报修人、故障类型为必填项')

        vals = {
            'equipment_id': int(equipment_id),
            'repair_content': repair_content,
            'reporter_id': int(reporter_id),
            'contact_phone': contact_phone,
            'fault_type': fault_type,
            'urgency': urgency,
            'estimated_cost': float(estimated_cost),
            'remark': remark
        }

        repair = request.env['device.repair'].sudo().create(vals)
        return {
            'code': 200,
            'msg': '查询成功',
            'data': {'repairId': repair.id}
        }

    @http.route('/api/repair/edit', type='json', auth='none', methods=['POST'], csrf=False, cors='*')
    # @api_response
    @verify_api_token
    # @check_api_permission('device:repair:edit')  # 已注释按钮权限，改用部门权限
    @check_department_permission
    def edit_repair(self, **kwargs):
        """修改报修记录"""
        repair_id = kwargs.get('repairId')
        if not repair_id:
            raise ValidationError('报修记录ID不能为空')

        repair = request.env['device.repair'].sudo().browse(int(repair_id))
        if not repair.exists():
            raise ValidationError('报修记录不存在')

        vals = {}
        if 'equipmentId' in kwargs:
            vals['equipment_id'] = int(kwargs['equipmentId'])
        if 'repairContent' in kwargs:
            vals['repair_content'] = kwargs['repairContent']
        if 'reporterId' in kwargs:
            vals['reporter_id'] = int(kwargs['reporterId'])
        if 'contactPhone' in kwargs:
            vals['contact_phone'] = kwargs['contactPhone']
        if 'faultType' in kwargs:
            vals['fault_type'] = kwargs['faultType']
        if 'urgency' in kwargs:
            vals['urgency'] = kwargs['urgency']
        if 'assignedTo' in kwargs:
            vals['assigned_to'] = int(kwargs['assignedTo']) if kwargs['assignedTo'] else False
        if 'faultAnalysis' in kwargs:
            vals['fault_analysis'] = kwargs['faultAnalysis']
        if 'repairSolution' in kwargs:
            vals['repair_solution'] = kwargs['repairSolution']
        if 'repairProcess' in kwargs:
            vals['repair_process'] = kwargs['repairProcess']
        if 'repairResult' in kwargs:
            vals['repair_result'] = kwargs['repairResult']
        if 'estimatedCost' in kwargs:
            vals['estimated_cost'] = float(kwargs['estimatedCost'])
        if 'actualCost' in kwargs:
            vals['actual_cost'] = float(kwargs['actualCost'])
        if 'partsCost' in kwargs:
            vals['parts_cost'] = float(kwargs['partsCost'])
        if 'laborCost' in kwargs:
            vals['labor_cost'] = float(kwargs['laborCost'])
        if 'remark' in kwargs:
            vals['remark'] = kwargs['remark']

        repair.write(vals)

        return {
            'code': 200,
            'msg': '成功',
        }

    @http.route('/api/repair/delete', type='json', auth='none', methods=['POST'], csrf=False, cors='*')
    # @api_response
    @verify_api_token
    # @check_api_permission('device:repair:delete')  # 已注释按钮权限，改用部门权限
    @check_department_permission
    def delete_repair(self, **kwargs):
        """删除报修记录"""
        repair_ids = kwargs.get('repairIds', [])
        if not repair_ids:
            raise ValidationError('请选择要删除的报修记录')

        repairs = request.env['device.repair'].sudo().browse(repair_ids)
        repairs.unlink()

        return {
            'code': 200,
            'msg': '成功',
        }

    @http.route('/api/repair/export', type='http', auth='none', methods=['GET'], csrf=False, cors='*')
    @verify_api_token
    # @check_api_permission('device:repair:export')  # 已注释按钮权限，改用部门权限
    @check_department_permission
    def export_repair(self, **kwargs):
        """导出报修信息"""
        # 获取查询条件
        equipment_id = kwargs.get('equipmentId', '')
        equipment_name = kwargs.get('equipmentName', '')
        status = kwargs.get('status', '')
        fault_type = kwargs.get('faultType', '')
        urgency = kwargs.get('urgency', '')

        domain = []
        if equipment_id:
            domain.append(('equipment_id', '=', int(equipment_id)))
        if equipment_name:
            domain.append(('equipment_name', 'ilike', equipment_name))
        if status:
            domain.append(('status', '=', status))
        if fault_type:
            domain.append(('fault_type', '=', fault_type))
        if urgency:
            domain.append(('urgency', '=', urgency))

        repairs = request.env['device.repair'].sudo().search(domain)

        # 构建Excel数据
        import xlsxwriter
        output = io.BytesIO()
        workbook = xlsxwriter.Workbook(output)
        worksheet = workbook.add_worksheet('设备报修信息')

        # 设置标题
        headers = [
            '设备编号', '设备名称', '设备类别', '设备型号', '报修时间', '报修内容',
            '报修人', '联系电话', '故障类型', '紧急程度', '报修状态', '分派给',
            '开始维修时间', '完成维修时间', '停机时长(h)', '预估费用', '实际费用',
            '配件费用', '人工费用', '创建时间', '备注'
        ]

        # 写入标题
        for col, header in enumerate(headers):
            worksheet.write(0, col, header)

        # 写入数据
        for row, repair in enumerate(repairs, 1):
            status_dict = dict(repair._fields['status'].selection)
            fault_type_dict = dict(repair._fields['fault_type'].selection)
            urgency_dict = dict(repair._fields['urgency'].selection)

            data = [
                repair.equipment_code,
                repair.equipment_name,
                repair.equipment_category,
                repair.equipment_model,
                repair.repair_date.strftime('%Y-%m-%d %H:%M:%S') if repair.repair_date else '',
                repair.repair_content or '',
                repair.reporter_name,
                repair.contact_phone or '',
                fault_type_dict.get(repair.fault_type, repair.fault_type),
                urgency_dict.get(repair.urgency, repair.urgency),
                status_dict.get(repair.status, repair.status),
                repair.assigned_to.nick_name if repair.assigned_to else '',
                repair.repair_start_date.strftime('%Y-%m-%d %H:%M:%S') if repair.repair_start_date else '',
                repair.repair_end_date.strftime('%Y-%m-%d %H:%M:%S') if repair.repair_end_date else '',
                repair.downtime_hours,
                repair.estimated_cost,
                repair.actual_cost,
                repair.parts_cost,
                repair.labor_cost,
                repair.create_time.strftime('%Y-%m-%d %H:%M:%S') if repair.create_time else '',
                repair.remark or ''
            ]

            for col, value in enumerate(data):
                worksheet.write(row, col, value)

        workbook.close()
        output.seek(0)

        # 生成文件名
        filename = f"设备报修信息_{datetime.now().strftime('%Y%m%d_%H%M%S')}.xlsx"

        response = request.make_response(
            output.getvalue(),
            headers=[
                ('Content-Type', 'application/vnd.openxmlformats-officedocument.spreadsheetml.sheet'),
                ('Content-Disposition', f'attachment; filename="{filename}"')
            ]
        )
        output.close()
        return response

    @http.route('/api/repair/status/<int:repair_id>/<status>', type='json', auth='none', methods=['POST'], csrf=False,
                cors='*')
    # @api_response
    @verify_api_token
    # @check_api_permission('device:repair:edit')  # 已注释按钮权限，改用部门权限
    @check_department_permission
    def update_status(self, repair_id, status, **kwargs):
        """更新报修状态"""
        repair = request.env['device.repair'].sudo().browse(repair_id)
        if not repair.exists():
            raise ValidationError('报修记录不存在')

        if status == 'confirmed':
            repair.action_confirm_repair()
        elif status == 'assigned':
            repair.action_assign_repair()
        elif status == 'repairing':
            repair.action_start_repair()
        elif status == 'completed':
            repair.action_complete_repair()
        elif status == 'cancelled':
            repair.action_cancel_repair()
        elif status == 'rejected':
            repair.action_reject_repair()
        else:
            repair.write({'status': status})

        return {
            'code': 200,
            'msg': '成功',
        }
